import React, { useEffect, useRef } from 'react';
import * as d3 from 'd3';

/**
 * 布局预览组件 - 使用D3.js渲染不同布局的小型预览
 */
const LayoutPreview = ({ layoutType, width = 120, height = 80 }) => {
  const svgRef = useRef(null);
  
  // 生成示例数据
  const generateSampleData = () => {
    // 为不同布局生成适合的示例数据
    const nodeCount = layoutType === 'grid' ? 9 : 6;
    
    const nodes = Array.from({ length: nodeCount }, (_, i) => ({
      id: `node_${i}`,
      name: `节点${i+1}`
    }));
    
    let links = [];
    
    switch (layoutType) {
      case 'force':
        // 力导向布局 - 随机连接
        links = [
          { source: 'node_0', target: 'node_1' },
          { source: 'node_0', target: 'node_2' },
          { source: 'node_1', target: 'node_3' },
          { source: 'node_2', target: 'node_4' },
          { source: 'node_3', target: 'node_5' }
        ];
        break;
      case 'circular':
        // 环形布局 - 环状连接
        for (let i = 0; i < nodes.length; i++) {
          links.push({
            source: `node_${i}`,
            target: `node_${(i + 1) % nodes.length}`
          });
        }
        break;
      case 'hierarchical':
      case 'tree':
        // 层次/树形布局 - 树状连接
        links = [
          { source: 'node_0', target: 'node_1' },
          { source: 'node_0', target: 'node_2' },
          { source: 'node_1', target: 'node_3' },
          { source: 'node_1', target: 'node_4' },
          { source: 'node_2', target: 'node_5' }
        ];
        break;
      case 'radial':
        // 辐射布局 - 中心辐射连接
        for (let i = 1; i < nodes.length; i++) {
          links.push({
            source: 'node_0',
            target: `node_${i}`
          });
        }
        break;
      case 'grid':
        // 网格布局 - 网格连接
        for (let i = 0; i < 3; i++) {
          for (let j = 0; j < 2; j++) {
            const idx = i * 3 + j;
            if (j < 2) {
              links.push({
                source: `node_${idx}`,
                target: `node_${idx + 1}`
              });
            }
            if (i < 2) {
              links.push({
                source: `node_${idx}`,
                target: `node_${idx + 3}`
              });
            }
          }
        }
        break;
      default:
        // 默认随机连接
        for (let i = 0; i < nodes.length - 1; i++) {
          links.push({
            source: `node_${i}`,
            target: `node_${i + 1}`
          });
        }
    }
    
    return { nodes, links };
  };

  useEffect(() => {
    if (!svgRef.current) return;
    
    // 清除之前的内容
    d3.select(svgRef.current).selectAll("*").remove();
    
    const { nodes, links } = generateSampleData();
    
    // 创建SVG
    const svg = d3.select(svgRef.current)
      .attr("width", width)
      .attr("height", height)
      .attr("viewBox", [0, 0, width, height]);
    
    // 创建连线元素
    const link = svg.append("g")
      .selectAll("line")
      .data(links)
      .join("line")
      .attr("stroke", "#999")
      .attr("stroke-opacity", 0.6)
      .attr("stroke-width", 1);
    
    // 创建节点元素
    const node = svg.append("g")
      .selectAll("circle")
      .data(nodes)
      .join("circle")
      .attr("r", 4)
      .attr("fill", "#69b3a2");
    
    // 根据布局类型应用不同的布局算法
    let simulation, radius, treeLayout, stratify, root, horizontalTree;
    let treeStratify, treeRoot, radialTree, radialStratify, radialRoot;
    let gridSize, cellWidth, cellHeight;
    
    switch (layoutType) {
      case 'force':
        // 力导向布局
        simulation = d3.forceSimulation(nodes)
          .force("link", d3.forceLink(links).id(d => d.id).distance(30))
          .force("charge", d3.forceManyBody().strength(-50))
          .force("center", d3.forceCenter(width / 2, height / 2))
          .on("tick", () => {
            link
              .attr("x1", d => Math.max(4, Math.min(width - 4, d.source.x)))
              .attr("y1", d => Math.max(4, Math.min(height - 4, d.source.y)))
              .attr("x2", d => Math.max(4, Math.min(width - 4, d.target.x)))
              .attr("y2", d => Math.max(4, Math.min(height - 4, d.target.y)));
            
            node
              .attr("cx", d => Math.max(4, Math.min(width - 4, d.x)))
              .attr("cy", d => Math.max(4, Math.min(height - 4, d.y)));
          });
        
        // 只运行少量迭代以提高性能
        for (let i = 0; i < 30; ++i) simulation.tick();
        simulation.stop();
        break;
        
      case 'circular':
        // 环形布局
        radius = Math.min(width, height) / 2 - 10;
        nodes.forEach((node, i) => {
          const angle = (i / nodes.length) * 2 * Math.PI;
          node.x = width / 2 + radius * Math.cos(angle);
          node.y = height / 2 + radius * Math.sin(angle);
        });
        
        link
          .attr("x1", d => d.source.x)
          .attr("y1", d => d.source.y)
          .attr("x2", d => d.target.x)
          .attr("y2", d => d.target.y);
        
        node
          .attr("cx", d => d.x)
          .attr("cy", d => d.y);
        break;
        
      case 'hierarchical':
        // 层次布局
        treeLayout = d3.tree().size([width - 10, height - 10]);
        
        // 创建层次结构
        stratify = d3.stratify()
          .id(d => d.id)
          .parentId(d => {
            const link = links.find(l => l.target === d.id);
            return link ? link.source : null;
          });
        
        root = stratify(nodes);
        treeLayout(root);
        
        // 更新节点和连线位置
        link
          .attr("x1", d => {
            const sourceNode = root.descendants().find(n => n.id === d.source);
            return sourceNode ? sourceNode.x + 5 : 0;
          })
          .attr("y1", d => {
            const sourceNode = root.descendants().find(n => n.id === d.source);
            return sourceNode ? sourceNode.y + 5 : 0;
          })
          .attr("x2", d => {
            const targetNode = root.descendants().find(n => n.id === d.target);
            return targetNode ? targetNode.x + 5 : 0;
          })
          .attr("y2", d => {
            const targetNode = root.descendants().find(n => n.id === d.target);
            return targetNode ? targetNode.y + 5 : 0;
          });
        
        node
          .attr("cx", d => {
            const treeNode = root.descendants().find(n => n.id === d.id);
            return treeNode ? treeNode.x + 5 : 0;
          })
          .attr("cy", d => {
            const treeNode = root.descendants().find(n => n.id === d.id);
            return treeNode ? treeNode.y + 5 : 0;
          });
        break;
        
      case 'tree':
        // 树形布局 (水平方向)
        horizontalTree = d3.tree().size([height - 10, width - 30]);
        
        // 创建层次结构
        treeStratify = d3.stratify()
          .id(d => d.id)
          .parentId(d => {
            const link = links.find(l => l.target === d.id);
            return link ? link.source : null;
          });
        
        treeRoot = treeStratify(nodes);
        horizontalTree(treeRoot);
        
        // 更新节点和连线位置 (交换x和y坐标以水平显示)
        link
          .attr("x1", d => {
            const sourceNode = treeRoot.descendants().find(n => n.id === d.source);
            return sourceNode ? sourceNode.y + 15 : 0;
          })
          .attr("y1", d => {
            const sourceNode = treeRoot.descendants().find(n => n.id === d.source);
            return sourceNode ? sourceNode.x + 5 : 0;
          })
          .attr("x2", d => {
            const targetNode = treeRoot.descendants().find(n => n.id === d.target);
            return targetNode ? targetNode.y + 15 : 0;
          })
          .attr("y2", d => {
            const targetNode = treeRoot.descendants().find(n => n.id === d.target);
            return targetNode ? targetNode.x + 5 : 0;
          });
        
        node
          .attr("cx", d => {
            const treeNode = treeRoot.descendants().find(n => n.id === d.id);
            return treeNode ? treeNode.y + 15 : 0;
          })
          .attr("cy", d => {
            const treeNode = treeRoot.descendants().find(n => n.id === d.id);
            return treeNode ? treeNode.x + 5 : 0;
          });
        break;
        
      case 'radial':
        // 辐射布局
        radialTree = d3.tree()
          .size([2 * Math.PI, Math.min(width, height) / 2 - 15])
          .separation((a, b) => (a.parent === b.parent ? 1 : 2) / a.depth);
        
        // 创建层次结构
        radialStratify = d3.stratify()
          .id(d => d.id)
          .parentId(d => {
            const link = links.find(l => l.target === d.id);
            return link ? link.source : null;
          });
        
        radialRoot = radialStratify(nodes);
        radialTree(radialRoot);
        
        // 更新节点和连线位置 (极坐标转换)
        link
          .attr("x1", d => {
            const sourceNode = radialRoot.descendants().find(n => n.id === d.source);
            return sourceNode ? width/2 + sourceNode.y * Math.cos(sourceNode.x) : 0;
          })
          .attr("y1", d => {
            const sourceNode = radialRoot.descendants().find(n => n.id === d.source);
            return sourceNode ? height/2 + sourceNode.y * Math.sin(sourceNode.x) : 0;
          })
          .attr("x2", d => {
            const targetNode = radialRoot.descendants().find(n => n.id === d.target);
            return targetNode ? width/2 + targetNode.y * Math.cos(targetNode.x) : 0;
          })
          .attr("y2", d => {
            const targetNode = radialRoot.descendants().find(n => n.id === d.target);
            return targetNode ? height/2 + targetNode.y * Math.sin(targetNode.x) : 0;
          });
        
        node
          .attr("cx", d => {
            const treeNode = radialRoot.descendants().find(n => n.id === d.id);
            return treeNode ? width/2 + treeNode.y * Math.cos(treeNode.x) : 0;
          })
          .attr("cy", d => {
            const treeNode = radialRoot.descendants().find(n => n.id === d.id);
            return treeNode ? height/2 + treeNode.y * Math.sin(treeNode.x) : 0;
          });
        break;
        
      case 'grid':
        // 网格布局
        gridSize = Math.ceil(Math.sqrt(nodes.length));
        cellWidth = (width - 10) / gridSize;
        cellHeight = (height - 10) / gridSize;
        
        nodes.forEach((node, i) => {
          const row = Math.floor(i / gridSize);
          const col = i % gridSize;
          node.x = 5 + col * cellWidth + cellWidth / 2;
          node.y = 5 + row * cellHeight + cellHeight / 2;
        });
        
        link
          .attr("x1", d => d.source.x)
          .attr("y1", d => d.source.y)
          .attr("x2", d => d.target.x)
          .attr("y2", d => d.target.y);
        
        node
          .attr("cx", d => d.x)
          .attr("cy", d => d.y);
        break;
        
      default:
        // 默认随机位置
        nodes.forEach((node, i) => {
          node.x = Math.random() * width;
          node.y = Math.random() * height;
        });
        
        link
          .attr("x1", d => d.source.x)
          .attr("y1", d => d.source.y)
          .attr("x2", d => d.target.x)
          .attr("y2", d => d.target.y);
        
        node
          .attr("cx", d => d.x)
          .attr("cy", d => d.y);
    }
    
  }, [layoutType, width, height]);

  return (
    <svg ref={svgRef} className="layout-preview" style={{ background: '#f5f5f5', borderRadius: '4px' }}></svg>
  );
};

export default LayoutPreview;